<script lang="ts">
  import { computed, defineComponent, ref } from '@vue/composition-api';
  import WaterFlow from '@/components/common/oto-water-flow-new.vue';
  import { Dynamic, getDyamicList } from '@/api/dynamic';
  import OtoRadio, { RadioPropsType } from './components/radio.vue';
  import { onLoad, onPullDownRefresh, onReachBottom, onShow, useDomRef } from '@/hooks/uniapp-composition-hooks';
  import OtoPushButton from '@/components/common/oto-push-button.vue';
  // import { useRouter } from '@/constants/router';
  import { dynamicTypeList } from '@/enum/dynamic.enum';
  import OtoBarrage from '@/components/common/oto-barrage.vue';
  import OtoInput from '@/components/common/oto-input.vue';
  import { useGoEasyListen, useLoadConversations } from '@/hooks/go-easy.hooks';
  import { addMessage, getMessageBoardList, MessageBoardForLoop } from '@/api/message-board';
  import { Vue } from 'vue/types/vue';
  import { useStore } from '@/store';
  import { UserModule } from '@/store/modules/user.module';
  import { Message } from '@/libs';

  export enum LoadStatusEnum {
    LODING = 'loading',
    LOAD_MORE = 'loadmore',
    NO_MORE = 'nomore',
    LOADING_ERROR = 'loadingErro'
  }

  export type PageData = {
    loadStatus: LoadStatusEnum;
    current: number;
    size: number;
    total: number;
    lastId: number;
    type: number;
  };
  function wait(time = 150) {
    return new Promise((resolve) => {
      const id = setTimeout(() => {
        resolve(id);
      }, time);
    });
  }

  export default defineComponent({
    components: {
      WaterFlow,
      OtoRadio,
      OtoPushButton,
      OtoBarrage,
      OtoInput
    },
    setup(_) {
      // const router = useRouter();
      try {
        useGoEasyListen();
      } catch (error) {
        console.log(error);
      }

      interface OtoBarrageTypeVm extends Vue {
        start(commentList: MessageBoardForLoop[]): Promise<void>;
        init(commentList: MessageBoardForLoop[]): Promise<void>;
        userAddComment(comment: any): void;
      }

      interface OtoBarrageType {
        new (...args: any): {
          $vm: OtoBarrageTypeVm;
        };
      }

      // const otoRadio = useDomRef<typeof OtoRadio>('otoRadio');
      const otoBarrage = useDomRef<OtoBarrageType>('otoBarrage');

      function toGetMessageBoardList() {
        return getMessageBoardList().then((res) => {
          const messageBoardForLoop: MessageBoardForLoop[] = res.data.map((item) => {
            return {
              id: item.id,
              content: item.content,
              nickname: item.userInfo.nickName,
              avatarUrl: item.userInfo.avatarUrl
            };
          });
          otoBarrage.value.$vm.start(messageBoardForLoop);
        });
      }
      onShow(() => {
        useLoadConversations();
      });

      const pageData = ref<PageData>({
        loadStatus: LoadStatusEnum.LOAD_MORE,
        current: 1,
        size: 10,
        total: 0,
        lastId: 0,
        type: 0
      });

      const pages = computed(() => {
        return Math.ceil(pageData.value.total / pageData.value.size);
      });

      async function getDynamicListForPage(loadState = false) {
        // 防止多次触发加载
        if (pageData.value.loadStatus === LoadStatusEnum.LODING) return;

        // 全部刷新
        if (loadState) {
          return;
        }
        const { current, size, lastId, type } = pageData.value;

        // 没有更多了
        if (pages.value > 0 && current > pages.value) {
          pageData.value.loadStatus = LoadStatusEnum.NO_MORE;
          return;
        }
        // 进行加载
        pageData.value.loadStatus = LoadStatusEnum.LODING;

        await wait(350);

        getDyamicList(current, size, lastId, type)
          .then((res) => {
            const data = res.data;
            if (!data.list) {
              pageData.value.loadStatus = LoadStatusEnum.NO_MORE;
            }
            if (!pageData.value.lastId && data.list.length > 0) {
              pageData.value.lastId = data.list[0].id;
            }

            data.list = data.list.map((item) => {
              item.images = item.images
                .split(',')
                .map((imageItem) => {
                  const key = /a=(\S*)/;
                  const match = imageItem.match(key);
                  if (match && match[1]) {
                    try {
                      item.imageParams = JSON.parse(match[1]) as Dynamic['imageParams'];
                    } catch (err) {
                      console.log(err);
                    }
                  }
                  const str = imageItem.replace(key, '');
                  return str;
                })
                .join(',');
              return item;
            });

            pageData.value.total = data.total;

            // 判断是否时翻页
            if (current === 1) {
              list.value = data.list;

              if (data.list.length === 0) {
                pageData.value.loadStatus = LoadStatusEnum.NO_MORE;
                pageData.value.current += 1; // 页数加一
                return;
              }
            } else {
              data.list.forEach((item) => {
                list.value.push(item);
              });
            }

            // pageData.value.size = data.size; // 应该按照前端的size来
            if (current < pages.value) {
              // 加载更多
              pageData.value.loadStatus = LoadStatusEnum.LOAD_MORE;
              pageData.value.current += 1; // 页数加一
            } else {
              pageData.value.loadStatus = LoadStatusEnum.NO_MORE;
            }
          })
          .catch((err) => {
            // 出错了
            pageData.value.loadStatus = LoadStatusEnum.LOADING_ERROR;
            console.log('err', err);
          });
      }

      onLoad(async (options: string | Record<string, any> | undefined) => {
        console.log('getDynamicListForPage', options);
        await getDynamicListForPage();
        toGetMessageBoardList();
      });

      const list = ref<Dynamic[]>([]);

      const typeList = ref<RadioPropsType['list']>(dynamicTypeList);

      function loadMore() {
        console.log('加载更多');
        if (pageData.value.loadStatus === LoadStatusEnum.NO_MORE) return;
        getDynamicListForPage();
      }

      function refreshAll() {
        // 初始化pageData
        pageData.value = {
          current: 1,
          size: 10,
          total: 0,
          loadStatus: LoadStatusEnum.LOAD_MORE,
          lastId: 0,
          type: pageData.value.type
        };
        // 清空列表数据
        list.value = [];
      }

      onReachBottom(() => {
        console.log('触底');
        loadMore();
      });

      onPullDownRefresh(async () => {
        uni.showLoading({
          mask: true,
          title: '刷新中～'
        });
        refreshAll();
        try {
          await getDynamicListForPage();
        } catch (error) {
          console.error(error);
        }
        uni.hideLoading();
        uni.hideNavigationBarLoading();
        uni.stopPullDownRefresh();
        console.log('触发了');
      });

      function changeType(type: number) {
        refreshAll();
        pageData.value.type = type;
        getDynamicListForPage();
      }

      const userModule = useStore(UserModule);

      const user = computed(() => {
        return userModule.getUserInfo;
      });

      const comment = ref('');
      function doConfirm() {
        addMessage(comment.value).then((res) => {
          const newComment = {
            id: res.data.id,
            nickname: user.value.nickName,
            content: comment.value,
            avatarUrl: user.value.avatarUrl
          };
          otoBarrage.value.$vm.userAddComment(newComment);
          comment.value = '';
          Message.success('成功留言！');
        });
      }

      return {
        user,
        comment,
        list,
        typeList,
        pageData,
        pages,
        changeType,
        doConfirm
      };
    }
  });
</script>

<template>
  <view class="square">
    <view class="message-board">
      <view class="message-board-title">O₂留言板</view>
      <view class="message-board-body">
        <view class="message-barrage">
          <oto-barrage :refresh="barrageRefresh" ref="otoBarrage" />
        </view>
        <view class="message-board-comment">
          <image class="comment-avatar" :src="user.avatarUrl" mode="" />
          <oto-input
            class="comment-input"
            @confirm="doConfirm"
            placeholder="我也要留言..."
            v-model="comment"
            :maxlength="30"
          />
        </view>
      </view>
    </view>
    <view class="header">
      <oto-radio ref="otoRadio" :value="pageData.type" @input="changeType" :list="typeList" />
    </view>
    <view class="line"></view>
    <view class="list">
      <water-flow ref="followWaterFlow" :flow-list="list" :load-status="pageData.loadStatus" />
    </view>
    <oto-push-button />
  </view>
</template>

<style lang="scss" scoped>
  .square {
    padding-top: 20rpx;

    // 留言板
    .message-board {
      .message-board-title {
        padding-left: 32rpx;
        color: rgba(51, 51, 51, 1);
        font-size: 36rpx;
        font-weight: bold;
        // background-color: #f5f5f5;
      }
      .message-board-body {
        background: rgba(255, 255, 255, 1);
        .message-barrage {
          margin: 16rpx auto 0 auto;
          margin-top: 11rpx;
          width: 690rpx;
          color: rgba(80, 80, 80, 1);
          background: rgba(212.71, 232.98, 255, 1);
          border-radius: 23rpx;
          font-size: 28rpx;
        }

        .message-board-comment {
          margin: 18rpx 50rpx 16rpx 42rpx;
          display: flex;
          .comment-avatar {
            width: 61rpx;
            height: 61rpx;
            border-radius: 105rpx;
            background-color: cadetblue;
          }
          .comment-input {
            margin-left: 9rpx;
            flex: 1;
          }
        }
      }
    }

    .line {
      height: 16rpx;
      background: #f2f2f2;
    }

    .header {
      display: flex;
      justify-content: center;
      padding-top: 10rpx;
      padding-bottom: 10rpx;
    }

    .list {
    }
  }
</style>
